import React, { useEffect, useRef } from 'react';
import * as echarts from 'echarts';

/**
 * 资金流向图组件
 * 展示资金流入、流出和净流入关系
 * 
 * 功能：
 * 1. 左侧显示收入节点（红色）
 * 2. 右侧显示支出节点（绿色）
 * 3. 中间显示净流入节点（正值红色，负值绿色）
 * 4. 动画效果展示资金流向
 * 5. 交互式提示和点击事件
 */
const FundFlowChart = () => {
  const chartRef = useRef(null);

  useEffect(() => {
    const chartDom = chartRef.current;
    const myChart = echarts.init(chartDom);

    // 图表基本尺寸设置
    const chartWidth = 1000;  // 图表宽度
    const chartHeight = 500;  // 图表高度
    const centerCoord = [chartWidth / 2, chartHeight / 2];  // 中心点坐标
    const curveness = 0.2;  // 连线曲率

    /**
     * 动态计算节点坐标的函数
     * 可以根据节点数量自动计算合适的位置
     * 
     * @param {number} count - 节点数量
     * @param {number} startY - 起始Y坐标
     * @param {number} endY - 结束Y坐标
     * @param {number} x - X坐标
     * @returns {Array} - 计算好的坐标数组
     */
    const calculatePositions = (count, startY, endY, x) => {
      const positions = [];
      // 如果只有一个节点，放在中间
      if (count === 1) {
        positions.push([x, (startY + endY) / 2]);
      } 
      // 多个节点，均匀分布
      else if (count > 1) {
        const step = (endY - startY) / (count - 1);
        for (let i = 0; i < count; i++) {
          positions.push([x, startY + i * step]);
        }
      }
      return positions;
    };

    /**
     * 节点类别定义
     * 包含两种类别：流入（红色）和流出（绿色）
     */
    const categories = [{
        name: '流入',
        itemStyle: {
            normal: {
                // 使用渐变色增强视觉效果
                color: new echarts.graphic.LinearGradient(0, 0, 1, 0, [
                    { offset: 0, color: '#ff3030' },
                    { offset: 1, color: '#ff7070' }
                ]),
            }
        },
        label: {
            normal: {
                fontSize: '18',  // 字体大小
                color: '#ffffff'  // 白色文字
            }
        },
    }, {
        name: '流出',
        itemStyle: {
            normal: {
                // 使用渐变色增强视觉效果
                color: new echarts.graphic.LinearGradient(0, 0, 1, 0, [
                    { offset: 0, color: '#30ff30' },
                    { offset: 1, color: '#70ff70' }
                ]),
            }
        },
        label: {
            normal: {
                fontSize: '18',  // 字体大小
                color: '#ffffff'  // 白色文字
            }
        },
    }];

    /**
     * 流入节点数据
     * 对于不同数量的数据，可以动态计算position坐标：
     * 1. 固定X坐标（例如距离左边界100px）
     * 2. Y坐标根据节点数量均匀分布
     */
    const inflowNodesData = [
        { name: "收入1", value: 320, speed: '50kb/s' },
        { name: "收入2", value: 240, speed: '40kb/s' },
        { name: "收入3", value: 180, speed: '30kb/s' },
        { name: "收入4", value: 150, speed: '20kb/s' }
    ];
    
    // 计算收入节点位置
    const leftX = 100; // 左侧固定X坐标
    const inflowPositions = calculatePositions(
        inflowNodesData.length,  // 节点数量
        100,                     // 顶部边距
        chartHeight - 100,       // 底部边距
        leftX                    // X坐标
    );
    
    // 将计算好的坐标分配给节点
    const inflowNodes = inflowNodesData.map((node, index) => ({
        ...node,
        position: inflowPositions[index]
    }));

    /**
     * 流出节点数据
     * 对于不同数量的数据，可以动态计算position坐标：
     * 1. 固定X坐标（例如距离右边界100px，即chartWidth - 100）
     * 2. Y坐标根据节点数量均匀分布
     */
    // 定义支出节点的基础数据（不包含位置信息）
    const outflowNodesData = [
        { name: "支出1", value: 250, speed: '45kb/s' },
        { name: "支出2", value: 230, speed: '42kb/s' },
        { name: "支出3", value: 180, speed: '30kb/s' }
    ];
    
    // 使用calculatePositions函数计算支出节点的位置
    const rightX = chartWidth - 100; // 右侧固定X坐标
    const outflowPositions = calculatePositions(
        outflowNodesData.length,  // 节点数量
        100,                      // 顶部边距
        chartHeight - 100,        // 底部边距
        rightX                    // X坐标
    );
    
    // 将计算好的坐标分配给节点
    const outflowNodes = outflowNodesData.map((node, index) => ({
        ...node,
        position: outflowPositions[index]
    }));

    // 计算总流入和总流出
    const totalIn = inflowNodes.reduce((sum, item) => sum + item.value, 0);
    const totalOut = outflowNodes.reduce((sum, item) => sum + item.value, 0);
    const netFlow = totalIn - totalOut;  // 净流入值

    /**
     * 中心节点配置
     * 显示净流入金额，根据正负值显示不同颜色
     */
    const centerNode = {
        name: "净流入",
        value: centerCoord,  // 位于图表中心
        symbolSize: 120,  // 节点大小
        itemStyle: {
            normal: {
                // 根据净流入值选择颜色：正值红色，负值绿色
                color: netFlow >= 0 
                    ? new echarts.graphic.LinearGradient(0, 0, 1, 0, [
                        { offset: 0, color: '#ff3030' },
                        { offset: 1, color: '#ff7070' }
                    ])
                    : new echarts.graphic.LinearGradient(0, 0, 1, 0, [
                        { offset: 0, color: '#30ff30' },
                        { offset: 1, color: '#70ff70' }
                    ])
            }
        },
        label: {
            normal: {
                position: 'inside',
                formatter: `净流入\n${netFlow >= 0 ? '+' : ''}${netFlow}`,  // 显示带符号的净流入值
                fontSize: 20,  // 字体大小
                fontWeight: 'bold',
                color: '#ffffff'  // 白色文字
            }
        },
        itemValue: netFlow,  // 保存净流入值用于提示框
        nodeType: 'center'   // 标记节点类型
    };

    /**
     * 合并所有节点数据
     * 包括流入节点、流出节点和中心节点
     */
    const data = [
        // 流入节点数据处理
        ...inflowNodes.map(n => ({
            name: n.name,
            category: 0,  // 类别索引，对应categories数组
            value: n.position,  // 节点位置
            symbolSize: 70,  // 节点大小
            speed: n.speed,
            itemValue: n.value,  // 保存原始金额值
            nodeType: 'inflow',  // 标记节点类型
            label: {
                normal: {
                    show: true,
                    position: 'inside',  // 标签位置
                    formatter: `${n.name}\n${n.value}`,  // 标签内容格式
                    color: '#ffffff',  // 文字颜色
                    fontSize: 16,  // 字体大小
                    fontWeight: 'bold'
                }
            }
        })),
        // 流出节点数据处理
        ...outflowNodes.map(n => ({
            name: n.name,
            category: 1,  // 类别索引，对应categories数组
            value: n.position,  // 节点位置
            symbolSize: 70,  // 节点大小
            speed: n.speed,
            itemValue: n.value,  // 保存原始金额值
            nodeType: 'outflow',  // 标记节点类型
            label: {
                normal: {
                    show: true,
                    position: 'inside',  // 标签位置
                    formatter: `${n.name}\n${n.value}`,  // 标签内容格式
                    color: '#ffffff',  // 文字颜色
                    fontSize: 16,  // 字体大小
                    fontWeight: 'bold'
                }
            }
        })),
        centerNode  // 中心节点
    ];

    /**
     * 动画线条数据
     * 用于显示资金流动的动画效果
     */
    const linesData = [
        // 流入线条：从收入节点到中心节点
        ...inflowNodes.map(item => ([
            { coord: item.position },  // 起点坐标
            { coord: centerCoord }     // 终点坐标（中心点）
        ])),
        // 流出线条：从中心节点到支出节点
        ...outflowNodes.map(item => ([
            { coord: centerCoord },    // 起点坐标（中心点）
            { coord: item.position }   // 终点坐标
        ]))
    ];

    /**
     * 节点连接关系
     * 定义节点之间的连线
     */
    const links = [
        // 流入连线：从收入节点到中心节点
        ...inflowNodes.map(item => ({
            source: item.name,  // 源节点名称
            target: centerNode.name,  // 目标节点名称
            value: item.value,  // 连线值（金额）
            lineStyle: {
                normal: {
                    color: '#ff3030',  // 红色
                    curveness: curveness,  // 曲率
                    width: 3  // 线宽
                }
            }
        })),
        // 流出连线：从中心节点到支出节点
        ...outflowNodes.map(item => ({
            source: centerNode.name,  // 源节点名称
            target: item.name,  // 目标节点名称
            value: item.value,  // 连线值（金额）
            lineStyle: {
                normal: {
                    color: '#30ff30',  // 绿色
                    curveness: curveness,  // 曲率
                    width: 3  // 线宽
                }
            }
        }))
    ];

    /**
     * 图表配置项
     */
    const option = {
        backgroundColor: 'transparent',  // 背景透明
        title: {
            show: false,  // 显示标题
            text: '资金流向图',
            left: 'center',
            textStyle: {
                color: '#ffffff',  // 白色文字
                fontSize: 24,  // 字体大小
                fontWeight: 'bold'
            }
        },
        // 提示框配置
        tooltip: {
            trigger: 'item',  // 触发类型：数据项
            backgroundColor: 'rgba(50,50,50,0.9)',
            borderColor: '#ccc',
            borderWidth: 1,
            padding: 10,
            textStyle: {
                color: '#fff',
                fontSize: 14
            },
            formatter: function(params) {
                // 根据节点类型显示不同的提示内容
                if (params.data.nodeType === 'inflow') {
                    return `<div style="font-weight:bold;font-size:16px;">${params.name}</div>
                            <div>金额: ${params.data.itemValue}</div>
                            <div>类型: 收入</div>
                            <div>可根据实际情况扩展...</div>`;
                } else if (params.data.nodeType === 'outflow') {
                    return `<div style="font-weight:bold;font-size:16px;">${params.name}</div>
                            <div>金额: ${params.data.itemValue}</div>
                            <div>类型: 支出</div>
                            <div>可根据实际情况扩展...</div>`;
                } else if (params.data.nodeType === 'center') {
                    return `<div style="font-weight:bold;font-size:16px;">净流入</div>
                            <div>金额: ${params.data.itemValue}</div>
                            <div>可根据实际情况扩展...</div>`;
                } else if (params.dataType === 'edge') {
                    return `<div>流向: ${params.data.source} → ${params.data.target}</div>
                            <div>金额: ${params.data.value}</div>
                            <div>可根据实际情况扩展...</div>`;
                }
                return '可根据实际情况扩展...';
            }
        },
        // 图例配置
        legend: {
            data: ['流入', '流出'],
            bottom: 10,
            itemWidth: 20,  // 图例标记宽度
            itemHeight: 14,  // 图例标记高度
            selectedMode: false,  // 禁止图例点击
            textStyle: {
                color: '#ffffff',  // 白色文字
                fontSize: 16  // 字体大小
            }
        },
        // X轴配置（隐藏）
        xAxis: {
            show: false,
            type: 'value',
            min: 0,
            max: chartWidth
        },
        // Y轴配置（隐藏）
        yAxis: {
            show: false,
            type: 'value',
            min: 0,
            max: chartHeight
        },
        // 系列列表
        series: [
            // 关系图系列
            {
                type: 'graph',  // 图表类型：关系图
                layout: 'none',  // 布局：不使用自动布局，使用指定的坐标
                coordinateSystem: 'cartesian2d',  // 坐标系：二维直角坐标系
                symbolSize: 70,  // 节点大小
                z: 3,  // 层级
                edgeLabel: {
                    normal: {
                        show: true,
                        textStyle: {
                            fontSize: 16,  // 边缘标签字体大小
                            color: '#ffffff'  // 白色文字
                        },
                        formatter: params => params.data.value ? `${params.data.value}` : ''
                    }
                },
                label: {
                    normal: {
                        show: true,
                        position: 'bottom',
                        color: '#ffffff',  // 白色文字
                        fontSize: 16  // 字体大小
                    }
                },
                itemStyle: {
                    normal: {
                        shadowBlur: 15,  // 阴影模糊大小
                        shadowColor: 'rgba(0, 0, 0, 0.5)'  // 阴影颜色
                    }
                },
                lineStyle: {
                    normal: {
                        width: 3  // 线宽
                    }
                },
                edgeSymbol: ['none', 'arrow'],  // 边两端的标记类型：无、箭头
                edgeSymbolSize: 12,  // 边两端的标记大小
                data: data,  // 节点数据
                links: links,  // 连线数据
                categories: categories  // 节点分类
            },
            // 流入动画系列
            {
                name: '流入动画',
                type: 'lines',  // 图表类型：线图
                coordinateSystem: 'cartesian2d',  // 坐标系：二维直角坐标系
                z: 1,  // 层级
                effect: {
                    show: true,  // 显示特效
                    period: 4,  // 特效周期
                    trailLength: 0.7,  // 特效尾迹长度
                    symbol: "circle",  // 特效图形
                    color: '#ff3030',  // 特效颜色
                    symbolSize: 10  // 特效图形大小
                },
                lineStyle: {
                    normal: {
                        color: '#ff3030',  // 线条颜色
                        width: 0,  // 线条宽度（设为0是为了只显示动画效果）
                        curveness: curveness  // 曲率
                    }
                },
                data: linesData.slice(0, inflowNodes.length)  // 流入线条数据
            },
            // 流出动画系列
            {
                name: '流出动画',
                type: 'lines',  // 图表类型：线图
                coordinateSystem: 'cartesian2d',  // 坐标系：二维直角坐标系
                z: 1,  // 层级
                effect: {
                    show: true,  // 显示特效
                    period: 4,  // 特效周期
                    trailLength: 0.7,  // 特效尾迹长度
                    symbol: "circle",  // 特效图形
                    color: '#30ff30',  // 特效颜色
                    symbolSize: 10  // 特效图形大小
                },
                lineStyle: {
                    normal: {
                        color: '#30ff30',  // 线条颜色
                        width: 0,  // 线条宽度（设为0是为了只显示动画效果）
                        curveness: curveness  // 曲率
                    }
                },
                data: linesData.slice(inflowNodes.length)  // 流出线条数据
            }
        ]
    };

    // 应用配置项
    option && myChart.setOption(option);
    
    // 添加点击事件
    myChart.on('click', function(params) {
        // 根据节点类型显示不同的提示内容
        let message = '';
        
        if (params.data) {
            if (params.data.nodeType === 'inflow') {
                message = `${params.name}\n金额: ${params.data.itemValue}\n类型: 收入\n可根据实际情况扩展...`;
            } else if (params.data.nodeType === 'outflow') {
                message = `${params.name}\n金额: ${params.data.itemValue}\n类型: 支出\n可根据实际情况扩展...`;
            } else if (params.data.nodeType === 'center') {
                message = `净流入\n金额: ${params.data.itemValue}\n可根据实际情况扩展...`;
            } else if (params.dataType === 'edge') {
                message = `流向: ${params.data.source} → ${params.data.target}\n金额: ${params.data.value}\n可根据实际情况扩展...`;
            } else {
                message = '可根据实际情况扩展...';
            }
        } else {
            message = '可根据实际情况扩展...';
        }
        
        // 显示提示框
        alert(message);
    });
    
    // 监听窗口大小变化，调整图表大小
    window.addEventListener('resize', () => {
      myChart.resize();
    });
    
    // 组件卸载时清理事件监听和图表实例
    return () => {
      window.removeEventListener('resize', () => {
        myChart.resize();
      });
      myChart.dispose();
    };
  }, []);  // 空依赖数组，组件挂载时执行一次

  // 渲染图表容器
  return <div 
    ref={chartRef} 
    style={{ 
      width: '100%',
      height: '100%'
    }}>
  </div>;
};

export default FundFlowChart;